package com.zjw.zy.coreui.view

import android.animation.Animator
import android.animation.AnimatorListenerAdapter
import android.annotation.SuppressLint
import android.content.Context
import android.graphics.Canvas
import android.graphics.Color
import android.graphics.drawable.Drawable
import android.util.AttributeSet
import android.view.Gravity
import android.view.View
import android.widget.LinearLayout
import android.widget.TextView
import com.baidu.ocr.sdk.utils.LogUtil
import com.zjw.zy.R
import com.zjw.zy.base.EventViewGroup
import com.zjw.zy.utils.AnimationUtils
import kotlin.math.min

/**
 * @author ：zhong.jw
 * @date ：Created in 2023/2/3 13:15
 *
 * 单选按钮组
 */
class RadioButtonGroup : EventViewGroup {

    companion object {
        private const val TAG = "RadioButtonGroup"

        const val EVENT_ITEM_CLICK = 1
    }


    private var itemUnselectColor: Int? = null
    private var itemSelectColor: Int? = null
    private var itemSize: Float? = null
    private var selectColor: Drawable? = null
    private var textArray: Array<CharSequence>? = null
    private var isVertical: Boolean = false
    private var count: Int = 0
    private val itemContent: LinearLayout by lazy { findViewById(R.id.radio_group_item_content) }
    private val shadow: View by lazy { findViewById(R.id.radio_group_select_shadow) }
    private var isLoaded = false
    private var selectIndex = -1

    constructor(context: Context?) : super(context) {}
    constructor(context: Context?, attrs: AttributeSet?) : super(context, attrs) {}
    constructor(context: Context?, attrs: AttributeSet?, defStyleAttr: Int) : super(
        context,
        attrs,
        defStyleAttr
    ) {
    }


    override fun onAttrs(context: Context, attrs: AttributeSet?) {
        val typeArray =
            context.obtainStyledAttributes(attrs, R.styleable.RadioButtonGroup)

        textArray = typeArray.getTextArray(R.styleable.RadioButtonGroup_item_array)
        isVertical = typeArray.getBoolean(R.styleable.RadioButtonGroup_vertical, false)
        selectColor = typeArray.getDrawable(R.styleable.RadioButtonGroup_select_color)
        itemSelectColor =
            typeArray.getColor(R.styleable.RadioButtonGroup_item_select_color, Color.WHITE)
        itemUnselectColor =
            typeArray.getColor(R.styleable.RadioButtonGroup_item_un_select_color, Color.BLACK)

        itemSize =
            typeArray.getDimension(R.styleable.RadioButtonGroup_item_size, 22f)

        typeArray.recycle()
    }

    override fun onFinishInflate() {
        super.onFinishInflate()
        onLoadItem()
    }

    override fun onAttachedToWindow() {
        super.onAttachedToWindow()
        onLoadItem()
    }

    private fun onLoadItem() {
        if (isLoaded) {
            return
        }
        isLoaded = true
        shadow.background = selectColor

        itemContent.orientation = if (isVertical) {
            LinearLayout.VERTICAL
        } else {
            LinearLayout.HORIZONTAL
        }
        textArray?.let { array ->
            count = array.size
            val ly = createLayoutParams(isVertical)

            for (value in array) {
                TextView(context).apply {
                    this.text = value
                    this.gravity = Gravity.CENTER
                    this.textSize = itemSize ?: 22f
                    this.setOnClickListener {
                        onRadioGroupItemClick(value.toString(), it as TextView)
                    }
                    itemContent.addView(this, ly)
                }
            }

            setSelect(0, 0)
        }
    }

    /**
     * @param value:选中值
     * @param animationTime:动画时间
     * */
    fun setSelect(value: String, animationTime: Long = 200) {
        textArray?.indexOf(value)?.takeIf { it >= 0 }?.let { setSelect(it, animationTime) }
    }

    /**
     * @param index:选中值下标
     * @param animationTime:动画时间
     * */
    fun setSelect(index: Int, animationTime: Long = 200) {
        index.takeIf { it >= 0 && it < textArray?.size ?: 0 && it != selectIndex }?.run {
            performSelectItem(this, animationTime)
        }
    }

    @SuppressLint("NewApi")
    private fun performSelectItem(select: Int, animationTime: Long) {
        selectIndex = select
        if (animationTime <= 0) {
            if (isVertical) {
                shadow.translationY = (shadow.height * select).toFloat()
            } else {
                shadow.translationX = (shadow.width * select).toFloat()
            }

            changeTextColor(select)
            return
        }
        //计算偏差
        if (isVertical) {
            AnimationUtils.objectAnimationOfY(shadow, (shadow.height * select).toFloat())
                .duration(min(0L, animationTime))
                .autoCancel(false)
                .addListener(object : AnimatorListenerAdapter() {
                    override fun onAnimationEnd(animation: Animator?) {
                        changeTextColor(select)
                    }
                })
                .start()
        } else {
            AnimationUtils.objectAnimationOfX(shadow, (shadow.width * select).toFloat())
                .duration(200)
                .addListener(object : AnimatorListenerAdapter() {
                    override fun onAnimationEnd(animation: Animator?) {
                        changeTextColor(select)
                    }
                })
                .autoCancel(false)
                .start()
        }
    }

    private fun changeTextColor(select: Int) {
        for (i in 0..itemContent.childCount) {
            (itemContent.getChildAt(i) as? TextView)
                ?.setTextColor(
                    if (select == i) {
                        itemSelectColor!!
                    } else {
                        itemUnselectColor!!
                    }
                )
        }
    }

    private fun onRadioGroupItemClick(value: String, view: TextView) {
        LogUtil.d(TAG, "click -> $value")

        //todo test
        setSelect(value)

        sendEvent(EVENT_ITEM_CLICK, value)
    }

    override fun onDraw(canvas: Canvas?) {
        super.onDraw(canvas)

        if (count <= 0) {
            return
        }

        val ly = shadow.layoutParams
        if (isVertical) {
            ly.height = (measuredHeight.toFloat() / count).toInt()
        } else {
            ly.width = (measuredWidth.toFloat() / count).toInt()
        }

        shadow.layoutParams = ly
    }

    private fun createLayoutParams(vertical: Boolean): LinearLayout.LayoutParams {
        val ly = LinearLayout.LayoutParams(
            LinearLayout.LayoutParams.MATCH_PARENT,
            LinearLayout.LayoutParams.MATCH_PARENT
        )
        ly.weight = 1f
        if (vertical) {
            ly.height = 0
        } else {
            ly.width = 0
        }
        return ly
    }

    override fun onLayoutId(): Int {
        return R.layout.layout_radio_button_group
    }

    override fun onBindListener() {
    }

    override fun onBindValue() {
    }

    override fun onFindView(rootView: View?) {
    }
}